import Vue from 'vue'
import Router from 'vue-router'
import store from '@/store/index'
import { userActions } from '@/utils/actionName'
import { componentMap } from '@/utils/routeComponentMap'


const { GET_USERINFO, GENERATE_FINALROUTES } = userActions

// 解决vue-router重复点击菜单报错的问题，重写 push 方法
const originalPush = Router.prototype.push
Router.prototype.push = function push(location) {
  return originalPush.call(this, location).catch(err => err)
}
// 重写 replace 方法
const originalReplace = Router.prototype.replace
Router.prototype.replace = function replace(location, onResolve, onReject) {
  if (onResolve || onReject) return originalReplace.call(this, location, onResolve, onReject)
  return originalReplace.call(this, location).catch(err => err)
}

Vue.use(Router)

// 静态路由表，不需要动态判断权限的路由，如登录页、404、等通用页面
export const constRoutes = [
  {
    path: '/login',
    component: () => import('views/Login'),
    meta: {
      title: 'login',
      hidden: true,  // 代表在遍历菜单时不显示在菜单栏上
    }
  },
  {
    path: '/test',
    component: () => import('views/test3'),
    meta: {
      title: 'test',
      hidden: true,  // 代表在遍历菜单时不显示在菜单栏上
    }
  },
  {
    path: '/401',
    component: () => import('views/401'),
    meta: {
      title: '401',
      hidden: true,  // 代表在遍历菜单时不显示在菜单栏上
    }
  },
  {
    path: '/',
    redirect: '/mimi',
    component: componentMap.Main, // 一级路由提供布局
    meta: { title: 'Main', hidden: false, icon: 'Main' },
    children: [
      // {
      //   path: 'home',
      //   name: 'Home',
      //   component: () => import('../views/home/Home'), // 二级路由提供真正的内容
      //   meta: {
      //     title: 'Home',
      //     // 当 设置 true 的时候该路由不会在侧边栏出现，如 401，login等页面，或者一些编辑页面 /edit/1
      //     hidden: false,
      //     icon: 'el-icon-s-home'
      //   }
      // }
      // {
      //   path: '/system',
      //   component: () => import('../views/Lay'),
      //   redirect: '/system/list',
      //   meta: { title: 'System', hidden: false, icon: 'System' },
      //   children: [
      //     {
      //       path: 'list',
      //       name: 'SystemList',
      //       component: () => import('../views/system/List'),
      //       meta: { title: 'System_list', hidden: false }
      //     },
      //     {
      //       path: 'add',
      //       name: 'SystemAdd',
      //       component: () => import('../views/system/Add'),
      //       // activeMenu: '/system/list'  当路由设置了该属性，则会高亮相对应的侧边栏
      //       // 这在某些场景非常有用，如 一个系统的列表页路由为： /system/list
      //       // 点击列表进入列表详情页，这时候路由为 /system/1 ，但你想在侧边栏高亮系统列表的路由，就可以进行如下设置
      //       meta: { title: 'SystemAdd', activeMenu: '/system/list', hidden: true }
      //     },
      //     {
      //       path: 'edit/:id',
      //       name: 'SystemEdit',
      //       component: () => import('../views/system/Edit'),
      //       // hidden: true 不在侧边栏上
      //       meta: { title: 'SystemEdit', activeMenu: '/system/list', hidden: true }
      //     }
      //   ]
      // },
      // {
      //   path: '/mimi',
      //   // component: componentMap.Lay,
      //   component: () => import('../views/Lay'),
      //   redirect: '/mimi/list',
      //   meta: { title: 'Mimi', hidden: false, icon: 'Mimi' },
      //   children: [
      //     {
      //       path: 'list',
      //       name: 'AssetsUdiskList',
      //       component: () => import('../views/mimi/assets/UdiskList'),
      //       meta: { title: 'Assets_udiskList', hidden: false }
      //     },
      //     {
      //       path: 'assets/terminalList',
      //       name: 'AssetsTerminalList',
      //       component: () => import('../views/mimi/assets/TerminalList'),
      //       meta: { title: 'Assets_terminalList', hidden: false }
      //     },
      //     {
      //       path: 'assets/printerList',
      //       name: 'AssetsPrinterList',
      //       component: () => import('../views/mimi/assets/PrinterList'),
      //       meta: { title: 'Assets_printerList', hidden: false }
      //     },
      //     {
      //       path: 'assets/burnerList',
      //       name: 'AssetsBurnerList',
      //       component: () => import('../views/mimi/assets/BurnerList'),
      //       meta: { title: 'Assets_burnerList', hidden: false }
      //     },
      //     {
      //       path: 'person/personList',
      //       name: 'PersonPersonList',
      //       component: () => import('../views/mimi/person/PersonList'),
      //       meta: { title: 'Person_personList', hidden: false }
      //     },
      //   ]
      // },
      // {
      //   path: '/alarm',
      //   component: () => import('../views/Lay'),
      //   redirect: '/alarm/list',
      //   meta: { title: 'UdiskAlarm', hidden: false, icon: 'udiskAlarm' },
      //   children: [
      //     {
      //       path: 'list',
      //       name: 'UdiskAlarm',
      //       component: () => import('../views/alarm/userAlarm/UdiskAlarm'),
      //       meta: { title: 'Udisk_alarm', hidden: false }
      //     },
      //     {
      //       path: 'userAlarm/terminalAlarm',
      //       name: 'TerminalAlarm',
      //       component: () => import('../views/alarm/userAlarm/TerminalAlarm'),
      //       meta: { title: 'Terminal_alarm', hidden: false }
      //     },
      //   ]
      // },
      // {
      //   path: '/status',
      //   component: () => import('../views/Lay'),
      //   redirect: '/status/list',
      //   meta: { title: 'status', hidden: false, icon: 'udiskAlarm' },
      //   children: [
      //     {
      //       path: 'list',
      //       name: 'StorageUdiskList',
      //       component: () => import('../views/status/storage/UdiskList'),
      //       meta: { title: 'Storage_udiskList', hidden: false }
      //     },
      //     {
      //       path: 'terminal/list',
      //       name: 'TerminalList',
      //       component: () => import('../views/status/terminal/TerminalList'),
      //       meta: { title: 'Terminal_terminalList', hidden: false }
      //     },
      //     {
      //       path: 'storage/udiskInfo/:id',
      //       name: 'UdiskInfo',
      //       component: () => import('../views/status/storage/UdiskInfo'),
      //       meta: { title: 'udiskInfo', hidden: false }
      //     },
      //     {
      //       path: 'terminal/terminalInfo/:id',
      //       name: 'StatusTerminalInfo',
      //       component: () => import('../views/status/terminal/TerminalInfo'),
      //       meta: { title: 'terminalInfo', hidden: false }
      //     },
      //   ]
      // },
      // {
      //   path: '/userBehavior',
      //   component: () => import('../views/Lay'),
      //   redirect: '/userBehavior/list',
      //   meta: { title: 'userBehavior', hidden: false, icon: 'udiskAlarm' },
      //   children: [
      //     {
      //       path: 'list',
      //       name: 'UserList',
      //       component: () => import('../views/userBehavior/user/List'),
      //       meta: { title: 'User_userList', hidden: false }
      //     },
      //   ]
      // },
      // {
      //   path: '/config',
      //   component: () => import('../views/Lay'),
      //   redirect: '/config/list',
      //   meta: { title: 'terminalProcess', hidden: false, icon: 'udiskAlarm' },
      //   children: [
      //     {
      //       path: 'list',
      //       name: 'TerminalProcess',
      //       component: () => import('../views/config/TerminalProcess'),
      //       meta: { title: 'terminalProcess', hidden: false }
      //     },
      //   ]
      // },
    ]
  },
  // ==================测试路由开始=================
  
  // ==================测试路由结束=================
]


// 创建路由管理器对象，并添加静态路由表
const createRouter = () => new Router({
    routes: constRoutes
  })
const router = createRouter()

// 根据权限获取有效路由列表
export function parseRoutes (routes) {
  const res = routes.map(element => {
    if (element.children && element.children.length > 0) {
      element.children = parseRoutes(element.children)
    }
    element.component = componentMap[element.component]  // 根据组件名称查询对应的组件
    return element
  })
  return res
}

// 注册路由的前置守卫，用于控制页面访问权限
router.beforeEach(async (to, from, next) => {
  const vuexRoles = store.getters.roles
  const storedToken = window.sessionStorage.getItem('token')
  const storedUname = window.sessionStorage.getItem('uname')
  // 通过 token 判断有无登录状态
  if (storedToken && storedUname) {
    // 已登录且去往登录界面，跳转到首页
    if (to.path === '/login') {
      return next('/mimi')
    } else {
      // 判断是否已经获取了角色信息
      if (vuexRoles &&  vuexRoles.length > 0) {
        // 如果已经获取角色信息，则直接放行
        // 因为获取角色信息会设置能够访问的页面
        // 所以如果访问到没有路由规则对应的页面时会进到404
        next()
      } else {
        // 如果没获取，则进行获取角色信息
        const uroutes = await store
        .dispatch(`user/${GET_USERINFO}`, storedUname)
        .catch(err => console.log(err))
        // 添加根据权限生成的路由列表
        const routelist = parseRoutes(uroutes)
        routelist.push({
          path: '*',
          redirect: '/401',
          meta: {hidden: true}
        }) // 401
        // 设置用户最终路由列表
        store
        .dispatch(`user/${GENERATE_FINALROUTES}`, constRoutes)
        .catch(err => console.log(err))
        constRoutes.forEach(item => {
          if (item.path === '/') {
            item.children.push(...routelist)
          }
        })
        // console.log(store.state.user.finalURoutes)
        // 只添加动态生成的路由列表
        router.addRoutes([...routelist])
        // console.log(router.options)
        // 如果直接调用 next ，有可能 addRoutes 没有执行完成
        // 调用这个传参的方式，让其丢弃当前导航以相同路径进入一次前置守卫
        // 由于前置守卫判断那里我们已经获取了用户信息
        // 所以就直接走 next()了，这样多走一遍这个流程保证 addRoutes 完成
        next({ ...to, replace: true })
      }
    }
  } else {
    // 未登录去往登录界面，则直接放行
    if (to.path === '/login') {
      next()
    } else {
      // 未登录且去往其他界面，跳转到登录界面
      return next('/login')
    }
  }
})

// 导出路由管理器
export default router

// 导出重置路由对象方法（该方法，主要是在更改路由列表前使用）
// 因为旧的路由对象已经通过 addRoutes 在前置守卫中添加了路由列表
// 所以在权限编辑中修改了页面权限后，需要重新添加路由列表
// 这时，就需要用到该方法；用户登出时，也应该使用该方法
export function resetRouter () {
  const newRouter = createRouter()
  router.matcher = newRouter.matcher // 替换旧的 router 的 matcher
}

